import * as log from 'https://deno.land/std@0.145.0/log/mod.ts';
import { serve } from 'https://deno.land/std@v0.145.0/http/server.ts';
import { parseExpression } from './handler/expression.ts';
import { IErrorVo, IResponseVo } from './dto/common.ts';

async function beforeServe() {
  if (Deno.env.get('JIANMU_EXPRESSION_NETWORK_DISABLED') !== 'true') {
    return;
  }

  await Deno.run({
    // 允许响应
    // iptables -A OUTPUT -p tcp -m state --state ESTABLISHED -j ACCEPT
    cmd: [
      'iptables',
      '-A',
      'OUTPUT',
      '-p',
      'tcp',
      '-m',
      'state',
      '--state',
      'ESTABLISHED',
      '-j',
      'ACCEPT',
    ],
  }).status();

  await Deno.run({
    // 限制出网
    // iptables -A OUTPUT -j DROP
    cmd: ['iptables', '-A', 'OUTPUT', '-j', 'DROP'],
  }).status();
}

(async () => {
  await beforeServe();
  await serve(async (req) => {
    const { pathname } = new URL(req.url);
    log.info(`>>>>>>>>>>\t${new Date().toLocaleString()}`);
    log.info(`pathname: ${pathname}`);
    log.info(`method: ${req.method}`);

    let status: number = 200;
    let result: IResponseVo;
    try {
      const dto = await req.json();
      log.info(`request body: ${JSON.stringify(dto)}`);
      result = await parseExpression(dto);
    } catch (err) {
      status = 400;
      result = {
        message: decodeURIComponent(err.message),
      } as IErrorVo;
    }
    const respBody = JSON.stringify(result);
    log.info(`response body: ${respBody}`);
    log.info(`<<<<<<<<<<\t${new Date().toLocaleString()}`);

    return new Response(respBody, {
      headers: {
        'Content-Type': 'application/json;charset=UTF-8',
      },
      status,
    });
  });
})();
